package com.mos.iot.mqtt.listener;

import cn.hutool.core.util.StrUtil;
import com.mos.iot.mqtt.constants.MqttConstants;
import com.mos.iot.mqtt.listener.converter.MessageConverter;
import com.mos.iot.mqtt.listener.converter.MessageConverterRegistry;
import com.mos.iot.mqtt.listener.converter.impl.MqttJsonMessageConverter;
import com.mos.iot.mqtt.util.JsonUtil;
import lombok.Builder;
import lombok.Getter;
import lombok.Setter;
import org.eclipse.paho.client.mqttv3.MqttMessage;

import java.nio.charset.StandardCharsets;
import java.util.HashMap;
import java.util.Map;

@Getter
@Setter
@Builder
public class MqttTopicMessage {

    @Builder.Default
    private MessageConverter messageConverter = MessageConverterRegistry.INSTANCE.getMessageConverter(MqttJsonMessageConverter.class);

    private String clientId;

    private String topic;

    @Builder.Default
    private Map<String, String> topicParam = new HashMap<>();

    @Builder.Default
    private int qos = 0;

    @Builder.Default
    private boolean retained = false;

    private Object payload;

    public String getClientId() {
        return StrUtil.blankToDefault(clientId, MqttConstants.DEFAULT_CLIENT_ID);
    }

    public String getTopic() {
        return StrUtil.format(topic, topicParam);
    }

    public <T> T getPayload(Class<T> target) {
        return JsonUtil.parseObject(StrUtil.toString(payload), target);
    }

    public MqttMessage getOutMessage() {
        if (payload instanceof MqttMessage) {
            return (MqttMessage) payload;
        } else {
            String jsonStr = messageConverter.convertWithCheck(payload, String.class, null, true);
            if(StrUtil.isNotBlank(jsonStr)) {
                return new MqttMessage(jsonStr.getBytes(StandardCharsets.UTF_8));
            }
        }
        return null;
    }

    public String getResponseKey() {
        return getResponseKey(null);
    }

    public String getResponseKey(Integer serialNo) {
        return StrUtil.format("{}:{}:{}", getClientId(), getTopic(), serialNo);
    }

}
